'use strict';

const Controller = require('../lib/controller');

module.exports = class AdminController extends Controller {

  /**
   * @route admin.php?in=xxxx
   */
  async index() {
    const theUser = this.ctx.theUser;
    const theCache = this.ctx.app.theCache;

    if (!theUser.loggedIn || theUser.groupID != 1) {
      return this.ctx.redirect('default.asp');
    }

    this.ctx.locals.strTitle = this.ctx.__('administration');

    if (this.ctx.request.query.act === 'login') {
      return await this.adminLogin();
    }

    if (this.ctx.request.query.act === 'logout') {
      return await this.logout();
    }

    if (!this.ctx.session.admin) {
      // Admin has not logged in
      return await this.adminLoginForm();
    }

    // Admin has logged in
    switch (String(this.ctx.request.query.in)) {
      case 'settings':
        if (this.ctx.request.query.act == 'update') {
          await this.updateSettings();
        }

        await theCache.loadSettings();

        await this.ctx.render('admin/settings.ejs');
        break;
      case 'category':
        if (this.ctx.request.query.act) {
          await this.updateCategories();
        }

        await theCache.loadCategories();

        if (this.ctx.request.query.act != 'move' || this.ctx.request.query.target) {
          await this.ctx.render('admin/categories.ejs');
        }
        break;
      case 'group':
        if (this.ctx.request.query.act) {
          await this.updateUserGroup();
        }
        await theCache.loadUserGroup();
        await this.ctx.render('admin/userGroup.ejs');
        break;
      case 'smilies':
        if (this.ctx.request.query.act) {
          await this.updateSmilies();
        }
        await theCache.loadSmilies();
        await this.ctx.render('admin/smilies.ejs');
        break;
      case 'wordfilter':
        if (this.ctx.request.query.act) {
          await this.updateWordFilter();
        }
        await theCache.loadWordFilter();
        await this.ctx.render('admin/wordFilter.ejs');
        break;
      case 'database':
        let data = {
          info: {},
          strResult: '',
          arrBackup: [],
        };
        await this.ctx.render('admin/database.ejs', data);
        break;
      case 'attachment':
        await this.ctx.render('admin/attachment.ejs', {
          bShowParent: false,
          arrList: [],
        });
        break;
      case 'announce':
        await this.showAnnouncement();
        break;
      case 'links':
        await this.showLinks();
        break;
      case 'misc':
        await this.showMisc();
        break;
      default:
        switch (String(this.ctx.request.query.act)) {
          case 'closesite':
            if (this.ctx.session.admin) {
              await this.closeSite();
              this.ctx.redirect('?');
            }
            break;
          case 'opensite':
            if (this.ctx.session.admin) {
              await this.openSite();
              this.ctx.redirect('?');
            }
            break;
          default:
            await this.showGeneralInfo();
        }
    }

  }

  /**
   * @route admin.php?in=index&act=closesite
   */
  async closeSite() {
    if (Session('admin') == true) {
      /*Application.Lock();
      Application(lbsNamespace+"siteClosed")=true;
      Application.Unlock();
      Response.Redirect("?");*/
    }
  }

  /**
   * @route admin.php?in=index&act=opensite
   */
  async openSite() {
    if (Session('admin') == true) {
      /*Application.Lock();
      Application(lbsNamespace+"siteClosed")=undefined;
      Application.Unlock();
      Response.Redirect("?");*/
    }
  }

  /**
   * @route admin.php?in=index&act=main
   */
  async showGeneralInfo() {
    var serverInfo = {
      'software': '?',
      'ip': this.ctx.ip,
      'scriptEngine': `Node.js`,
      'time': this.ctx.helper.getDateTimeString('YY-MM-DD hh:ii:ss Z'),
      'path': process.cwd(),
      'objFSO': false,
      'objStream': false,
      'objXMLHTTP': false,
      'objXMLDOM': false,
    };
    await this.ctx.render('admin/generalInfo.ejs', {serverInfo, info: {}});
  }

  // Announcement Page /////////////////////////////////////////////////////////////////////////////////////
  async showAnnouncement() {
    const connBlog = this.ctx.app.connBlog;
    const theCache = this.ctx.app.theCache;

    // Update -------------
    if (this.ctx.request.query.act == 'update') {
      var ubbFlags = '';
      ubbFlags += this.ctx.request.body.e_ubb == 'true' ? '1' : '0';
      ubbFlags += this.ctx.request.body.e_autourl == 'true' ? '1' : '0';
      ubbFlags += this.ctx.request.body.e_image == 'true' ? '1' : '0';
      ubbFlags += this.ctx.request.body.e_media == 'true' ? '1' : '0';
      ubbFlags += this.ctx.request.body.e_smilies == 'true' ? '1' : '0';
      ubbFlags += '1'; // bTextBlock - always 1
      if (this.ctx.request.body.e_html == 'true') ubbFlags = 'html';
      await connBlog.updateSQL('blog_settings', 'set_value0=' + (this.ctx.request.body.show == 'true' ? 1 : 0),
        'set_name=\'announceShow\'');
      await connBlog.updateSQL('blog_settings', 'set_value1=\'' + ubbFlags + '\'', 'set_name=\'announceUBBFlags\'');
      await connBlog.updateSQL('blog_settings', 'set_value1=\'' + func.checkStr(this.ctx.request.query.message) + '\'',
        'set_name=\'announce\'');
      await connBlog.updateSQL('blog_settings', 'set_value1=\'' + func.getDateTimeString() + '\'',
        'set_name=\'announceDate\'');
    }

    await theCache.loadSettings();

    await this.ctx.render('admin/announcement.ejs', {});
  }

  // Links Page /////////////////////////////////////////////////////////////////////////////////////
  async showLinks() {
    const connBlog = this.ctx.app.connBlog;
    const theCache = this.ctx.app.theCache;

    // Update -------------
    if (this.ctx.request.query.act == 'update') {
      await connBlog.updateSQL('blog_settings', 'set_value1=\'' + func.checkStr(this.ctx.request.query.links) + '\'',
        'set_name=\'links\'');
    }

    await theCache.loadSettings();

    await this.ctx.render('admin/links.ejs', {});
  }

  // Misc Page /////////////////////////////////////////////////////////////////////////////////////
  async showMisc() {
    let tDate;
    const connBlog = this.ctx.app.connBlog;
    const connGBook = this.ctx.app.connBlog;
    const func = this.ctx.helper;
    const theCache = this.ctx.app.theCache;

    // Resync Global Counter
    if (this.ctx.request.query.act == 'resync_g') {
      var tmpA = await connBlog.query('SELECT count(log_id) as cnt FROM blog_article');
      await connBlog.updateSQL('blog_settings', 'set_value0=' + tmpA[0]['cnt'], 'set_name=\'counterArticle\'');
      tmpA = await connBlog.query('SELECT count(comm_id) as cnt FROM blog_comment');
      await connBlog.updateSQL('blog_settings', 'set_value0=' + tmpA[0]['cnt'], 'set_name=\'counterComment\'');
      tmpA = await connBlog.query('SELECT count(tb_id) as cnt FROM blog_trackback');
      await connBlog.updateSQL('blog_settings', 'set_value0=' + tmpA[0]['cnt'], 'set_name=\'counterTrackback\'');
      tmpA = await connBlog.query('SELECT count(user_id) as cnt FROM blog_user');
      await connBlog.updateSQL('blog_settings', 'set_value0=' + tmpA[0]['cnt'], 'set_name=\'counterUser\'');
      await theCache.loadSettings();
    }

    // Resync Category Counter
    if (this.ctx.request.query.act == 'resync_c') {
      var tmpA = await connBlog.query('SELECT cat_id FROM blog_category');
      if (tmpA) {
        for (var i = 0; i < tmpA.length; i++) {
          var tmpB = await connBlog.query(
            'SELECT count(log_id) as cnt FROM blog_article WHERE log_catid=' + tmpA[i]['cat_id']);
          await connBlog.updateSQL('blog_category', 'cat_articleCount=' + tmpB[0]['cnt'],
            'cat_id=' + tmpA[i]['cat_id']);
        }
      }
      await theCache.loadCategories();
    }

    // Resync Article Counter
    if (this.ctx.request.query.act == 'resync_a') {
      if (!this.ctx.request.query.start) {
        this.ctx.request.query.start = 1;
      } else {
        this.ctx.request.query.start = func.checkInt(this.ctx.request.query.start);
      }
      var tmpA;

      await connBlog.query('SELECT log_id FROM blog_article', 20, this.ctx.request.query.start);
      if (tmpA) {
        for (var i = 0; i < tmpA.length; i++) {
          var tmpB;

          await connBlog.query('SELECT count(comm_id) as cnt FROM blog_comment WHERE log_id=' + tmpA[i]['log_id']);
          await connBlog.updateSQL('blog_article', 'log_commentCount=' + tmpB[0]['cnt'],
            'log_id=' + tmpA[i]['log_id']);
          tmpB ==
          await connBlog.query('SELECT count(tb_id) as cnt FROM blog_trackback WHERE log_id=' + tmpA[i]['log_id']);
          await connBlog.updateSQL('blog_article', 'log_trackbackCount=' + tmpB[0]['cnt'],
            'log_id=' + tmpA[i]['log_id']);
        }
        const data = {
          strStep: this.ctx.__('resync_article_stats'),
          strEvent: this.ctx.__('processed') + (this.ctx.request.query.start * 20) + this.ctx.__('entries'),
          strRedirect: '?in=misc&act=resync_a&start=' + (this.ctx.request.query.start + 1),
        };
        await this.ctx.render('admin/event.ejs', data);

      } else {
        return this.ctx.redirect('?in=misc');
      }

      await theCache.loadArticles();
    }

    // Resync User Counter
    if (this.ctx.request.query.act == 'resync_u') {
      if (!this.ctx.request.query.start) {
        this.ctx.request.query.start = 1;
      } else {
        this.ctx.request.query.start = func.checkInt(this.ctx.request.query.start);
      }
      var tmpA = await connBlog.query('SELECT user_id FROM blog_user', 50, this.ctx.request.query.start);
      if (tmpA) {
        for (var i = 0; i < tmpA.length; i++) {
          var tmpB = await connBlog.query(
            'SELECT count(comm_id) as cnt FROM blog_comment WHERE comm_authorid=' + tmpA[i]['user_id']);
          await connBlog.updateSQL('blog_user', 'user_commentCount=' + tmpB[0]['cnt'],
            'user_id=' + tmpA[i]['user_id']);
          tmpB = await connBlog.query(
            'SELECT count(log_id) as cnt FROM blog_article WHERE log_authorid=' + tmpA[i]['user_id']);
          await connBlog.updateSQL('blog_user', 'user_articleCount=' + tmpB[0]['cnt'],
            'user_id=' + tmpA[i]['user_id']);
        }
        const data = {
          strStep: this.ctx.__('resync_user_stats'),
          strEvent: this.ctx.__('processed') + (this.ctx.request.query.start * 50) + this.ctx.__('entries'),
          strRedirect: '?in=misc&act=resync_u&start=' + (this.ctx.request.query.start + 1),
        };
        await this.ctx.render('admin/event.ejs', data);
      } else {
        this.ctx.redirect('?in=misc');
      }
    }

    // Clean Inactive User Account
    if (this.ctx.request.query.act == 'clean_u') {
      tDate = new Date();
      tDate.setTime(tDate.getTime() - 30 * 864E5);
      await connBlog.exec(
        'DELETE * FROM blog_user WHERE user_commentCount=0 AND user_articleCount=0 AND user_lastVisit<#' +
        func.getDateTimeString('YY-MM-DD hh:ii:ss', tDate) + '#');
      var tmpA = await connBlog.query('SELECT count(user_id) as cnt FROM blog_user');
      await connBlog.updateSQL('blog_settings', 'set_value0=' + tmpA[0]['cnt'], 'set_name=\'counterUser\'');
      await theCache.loadSettings();
    }

    // Clean Visitor Counter
    if (this.ctx.request.query.act == 'clean_vc') {
      await connBlog.exec('DELETE * FROM blog_visitorrecord');
    }

    // Clean GuestBook Entries
    if (this.ctx.request.query.act == 'clean_gb') {

      tDate = new Date();
      tDate.setTime(tDate.getTime() - 30 * 864E5);
      await connGBook.exec(
        'DELETE * FROM blog_guestbook WHERE gb_postTime<#' + func.getDateTimeString('YY-MM-DD hh:ii:ss', tDate) + '#');
    }

    // output Page
    await this.ctx.render('admin/misc.ejs', {});
  }

  /**
   * Admin has not logged in
   * @route admin.php?act=
   */
  async adminLoginForm() {
    await this.ctx.render('admin/adminLoginForm.ejs');
  }

  /**
   * @route admin.php?act=logout
   *
   */
  async logout() {
    this.ctx.session.admin = null;
    this.ctx.redirect('default.asp');
  }

  /**
   * Admin Login Check
   * @route admin.php?act=login
   */
  async adminLogin() {
    const connBlog = this.ctx.app.connBlog;
    const func = this.ctx.helper;
    const theUser = this.ctx.theUser;

    var tmpA = await connBlog.query('SELECT user_password, user_salt FROM blog_user WHERE user_id=' + theUser.id);
    if (!tmpA) {
      this.ctx.session.admin = null;

      return await this.ctx.response.redirectMessage(
        this.ctx.__('error'),
        this.ctx.__('user_not_found'),
        '',
        '',
        false,
        'errorbox',
      );

    }
    if (tmpA[0]['user_password'] != func.SHA1(this.ctx.request.body.password + tmpA[0]['user_salt'])) {
      this.ctx.session.admin = null;
      return await this.ctx.response.redirectMessage(
        this.ctx.__('error'),
        this.ctx.__('password_invalid'),
        '',
        '',
        false,
        'errorbox',
      );

    }
    this.ctx.session.admin = true;

  }
};
